#lang racket

(require racket/match)

(define builtins
  `((car . ,car)
    (cdr . ,cdr)
    (cons . ,cons)
    (+ . ,+)
    (- . ,-)
    (* . ,*)
    (/ . ,/)))

(define (i exp env)
  (match exp
    ((? number? n) n)
    ((? symbol? s)
     (cond ((assoc s env) => cdr)
	   (else (error "unbound variable" s))))
    ((? list? l)
     (apply (i (car l) env) (map (lambda (exp) (i exp env)) (cdr l))))
    (else (error "unknown expression type" exp))))

;; > (i '(+ 7 (car (cons 3 5))) builtins)
;; 10
